<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <title>tiptap collaborative 实时协作 - itxst.com</title>
    <meta name="keywords" content="tiptap collaborative 实时协作" />
    <meta name="description" content="tiptap 支持实时协作、让不同设备之间的同步和离线工作。通过与 Y.js 配合使用无需多少代码即可实现多人在线实时协作，不过在大部分的实践工作中，实时协作并不是一个强需求。" />
    <meta content="text/html; charset=utf-8" http-equiv="Content-Type" />
    <meta http-equiv="Content-Language" content="zh-CN">
    <link rel="shortcut icon" href="/img/favicon.ico" type="image/x-icon" />
    <link href="/css/zt.css?ver=1.6.6" rel="stylesheet" type="text/css" media="all" />
    <script type="text/javascript" language="javascript" src="/js/jquery.js?ver=1.6.6"></script>
    <script type="text/javascript" src="/js/highlight/highlight.min.js?ver=1.6.6"></script>
    <link rel="stylesheet" type="text/css" href="/js/highlight/styles/vs2015x.css?ver=1.6.6">
    <script type="text/javascript" language="javascript" src="/js/comm.js?ver=1.6.6"></script>
    <script type="text/javascript" language="javascript" src="/js/zt.js?ver=1.6.6"></script>
    <script type="text/javascript" charset="utf-8" src="/js/layer/layer.js?ver=1.6.6"></script>
    <link rel="alternate" media="only screen and(max-width: 640px)" href="http://m.itxst.com/tiptap/collaborative.html" >
    <!--[if lte IE 9]>
    <script src="/js/respond/respond.js?ver=1.6.6"></script>
    <![endif]-->
</head>
<body>
    <div class="body"  >
        <div class="header">
            <div class="naver">
                <div class="logo">
                    <a href="/"><img src="/img/logov31.png" /></a>
                </div>
                <div class="naver-left">
                 <a href="/tiptap/tutorial.html">tiptap 中文文档</a>
                </div>
                <div class="naver-search">
                    <div class="naver-search-txt">
                        <input type="text" id="keyword" placeholder="Please enter the keyword" data-topic="tiptap">
                    </div>
                    <div class="naver-search-btn"><a href="javascript:void(0)" onclick="Search()">Search</a></div>
                </div>
                 <div class="naver-right"> 
                        <a href="/ag-grid/tutorial.html">AG-GRID</a> 
                        <a href="/tiptap/tutorial.html">Tiptap</a> 
                        <a href="/css-flex/tutorial.html">CSS-FLEX</a> 
                        <a href="/Bootstrap-Table/QuickStart.html">Bootstrap-Table</a> 
                </div>
            </div>
            <div class="path">
                
            </div>
        </div>
        <div class="clearfix"></div>
        <div class="pagew">
        <div class="page" >
            <div class="page-body">
                <div class="content-detail">
                    <h1>tiptap collaborative 实时协作</h1>
               
               <p class="p"><strong>tiptap</strong> 支持<strong>实时协作</strong>、让不同设备之间的同步和离线工作。通过与 <strong>Y.js</strong> 配合使用无需多少代码即可实现多人在线实时协作，不过在大部分的实践工作中，实时协作并不是一个强需求。</p><h2>网络实时通信</h2><p class="p">WebRTC仅使用服务器让各个客户端（浏览器）击行相互通讯。服务器并不参与数据的传输。<br/>安装依赖项：<br/></p><pre class="brush:js;toolbar:false"><code class="language-javascript">npm install @tiptap/extension-collaboration yjs y-webrtc y-prosemirror</code></pre><p class="p">然后创建一个 Y 文档，并注册到 Tiptap：</p><pre class="brush:js;toolbar:false"><code class="language-javascript">import { WebrtcProvider } from 'y-webrtc'

// A new Y document
const ydoc = new Y.Doc()
// Registered with a WebRTC provider
const provider = new WebrtcProvider('example-document', ydoc)

const editor = new Editor({
  extensions: [
    StarterKit.configure({
      // The Collaboration extension comes with its own history handling
      history: false,
    }),
    // Register the document with Tiptap
    Collaboration.configure({
      document: ydoc,
    }),
  ],
})</code></pre><p class="p">到此为止你就可以让不同的用户进行实时协作了，它是如何运行的呢？WebRTC程序通过公共服务器将客户端连接在一起，服务器并不同步实际的更改，然而这个也有两个缺点。<br/>1，浏览器拒绝连接太多客户端，对于同一文档中超过 100+ 个并发客户端，它不能很好的支持。<br/>2，服务器没有参与文档记录的更改，因为WebRTC信令服务器不会收到更改，因此不知道文档中的内容。<br/>如果你想更深入地研究，请前往GitHub上的<a href="https://github.com/yjs/y-webrtc" target="_blank">Y WebRTC存储库</a></p><h2>WebSocket 推荐</h2><p class="p">对于大多数情况，tiptap建议使用 WebSocket ,因为它更灵活，也可以很好地扩展。为了更容易使用，tiptap发布了<a href="http://hocuspocus.dev/" target="_blank">Hocuspocus</a>作为Tiptap的官方后端程序。<br/><br/>对于客户端示例几乎相同，只不过驱动程序不同。首先，让我们安装依赖项：</p><pre class="brush:js;toolbar:false"><code class="language-javascript">npm install @tiptap/extension-collaboration @hocuspocus/provider y-prosemirror</code></pre><p class="p">然后向 Tiptap 注册 WebSocket 供应程序：</p><pre class="brush:js;toolbar:false"><code class="language-javascript">import { Editor } from '@tiptap/core'
import StarterKit from '@tiptap/starter-kit'
import Collaboration from '@tiptap/extension-collaboration'
import { HocuspocusProvider } from '@hocuspocus/provider'

// Set up the Hocuspocus WebSocket provider
const provider = new HocuspocusProvider({
  url: 'ws://127.0.0.1:1234',
  name: 'example-document',
})

const editor = new Editor({
  extensions: [
    StarterKit.configure({
      // The Collaboration extension comes with its own history handling
      history: false,
    }),
    // Register the document with Tiptap
    Collaboration.configure({
      document: provider.document,
    }),
  ],
})</code></pre><p class="p">如你所见此示例不是开箱即用的。它需要配置为与WebSocket服务器通信，因此需要安装WebSocket 后端程序<a href="http://hocuspocus.dev/" target="_blank">Hocuspocus</a>。</p><h2>WebSocket 后端</h2><p class="p">为了使服务器部分尽可能简单，tiptap提供了一个node.js的服务器包 Hocuspocus。它是一个灵活的 Node.js 包，可用于构建后端。<br/>下面的命令用来启动这个服务：</p><pre class="brush:ps;toolbar:false;"><code class="language-javascript">npx @hocuspocus/cli --port 1234 --sqlite</code></pre><p class="p">运行 Hocuspocus 命令行，启动侦听1234端口并将更改存储在内存中（一旦停止命令，它就会消失），输出如下所示：</p><pre class="brush:ps;toolbar:false;"><code class="language-javascript">Hocuspocus v1.0.0 running at:

&gt; HTTP: http://127.0.0.1:1234
&gt; WebSocket: ws://127.0.0.1:1234

Ready.</code></pre><p class="p">尝试在浏览器中打开 http://127.0.0.1:1234 网址，如果一切运行正常，你应该会看到一个纯文本。<br/>然后返回 Tiptap 编辑器并F5刷新网页，它将连接到 Hocuspocus WebSocket 服务器，这时就可以与其他用户进行实时协作了。<br/></p><h2>多个服务器</h2><p class="p">你可以注册多个服务器保证服务的稳定，当一个服务器宕机客户端将连接另外一个服务器</p><pre class="brush:js;toolbar:false"><code class="language-javascript">new WebrtcProvider('example-document', ydoc)
new HocuspocusProvider({
  url: 'ws://127.0.0.1:1234',
  name: 'example-document',
  document: ydoc,
})</code></pre><h2>显示光标</h2><p class="p">当多个人进行在线编辑，你可以设置每个人的昵称显示在编辑器光标位置</p><pre class="brush:js;toolbar:false"><code class="language-javascript">import { Editor } from '@tiptap/core'
import StarterKit from '@tiptap/starter-kit'
import Collaboration from '@tiptap/extension-collaboration'
import CollaborationCursor from '@tiptap/extension-collaboration-cursor'
import { HocuspocusProvider } from '@hocuspocus/provider'

// Set up the Hocuspocus WebSocket provider
const provider = new HocuspocusProvider({
  url: 'ws://127.0.0.1:1234',
  name: 'example-document',
})

const editor = new Editor({
  extensions: [
    StarterKit.configure({
      // The Collaboration extension comes with its own history handling
      history: false,
    }),
    Collaboration.configure({
      document: provider.document,
    }),
    // Register the collaboration cursor extension
    CollaborationCursor.configure({
      provider: provider,
      user: {
        name: 'Cyndi Lauper',
        color: '#f783ac',
      },
    }),
  ],
})</code></pre><h2>离线支持<br/></h2><p class="p">基于Y IndexedDB 你可以实现关闭浏览器后所有更改都将存储在浏览器中，下次联机时，WebSocket 提供程序将尝试查找连接并最终同步更改。</p><h2>其他设置</h2><p class="p">文档名称、身份验证授权、在线演示请访问官方文档<br/><a href="https://tiptap.dev/guide/collaborative-editing#the-document-name" target="_blank" textvalue="协作编辑 – 提示编辑器 (tiptap.dev)">协作编辑 – 提示编辑器 (tiptap.dev)</a></p>
 
               <h2>
    下载教程 Demo
</h2>
<p class="pe">
   本教程<b>Demo</b>的源码点击这里下载，<a href="https://img1.itxst.com/8/c/8c32fcdc12cb8847c62e405be8a73835.zip" target="_blank" textvalue="Tiptap Demo">Tiptap Demo</a>，下载完成后运行<b>npm i</b>初始化依赖包。
</p>
                </div>
                <div class="content-r">   <a href="/tiptap/tutorial.html" target="_self">
                     <img src="https://img1.itxst.com/0/9/09355b3592a0c16799b504a9f2a70303.png" alt="tiptap 中文文档" />
                    </a>                                                <a href="//www.itxst.com/vue-draggable/tutorial.html" target="_blank">
                                <img src="//img1.itxst.com/b/f/bf9af8368dfac84cd703ef54e1e89d14.png" alt="vue.draggable" />
                            </a>
 
                </div>
            </div>
            <div class="home-menu scroll">
                <div class="tree">
      <a data-level="1" class="leve-1   doc-1   " href="/tiptap/tutorial.html" title="tiptap 中文文档">快速入门</a>
      <a data-level="1" class="leve-1    arrow-2" href="/tiptap/configuration.html" title="Guide 向导">Guide 向导</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/configuration.html" title="Tiptap 编辑器 Configuration 配置">configuration 配置</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/roseMirrorapi.html" title="ProseMirror  API">prosemirror  api</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/menus.html" title="tiptap menus 菜单">menus 菜单</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/styling.html" title="Styling Titpap 样式">styling 样式</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/output.html" title="Titpap Output 输出格式">output 输出格式</a>
      <a data-level="2" class="leve-2   doc-1    doc-2 " href="/tiptap/collaborative.html" title="tiptap collaborative 实时协作">collaborative 实时协作</a>
      <a data-level="2" class="leve-2   doc-1   " href="/tiptap/customextensions.html" title="tiptap 自定义扩展">extensions 自定义扩展</a>
      <a data-level="1" class="leve-1    arrow-1" href="/tiptap/api.html" title="tiptap api 列表">API 列表</a>
                 </div>
                 <div  class="clearfix"></div>
            </div>
        </div>
        <div class="clearfix"></div>
           <div class="footer">
© 2023 itxst.com All rights reserved.
</div>

<script>
var _hmt = _hmt || [];
(function() {
  var hm = document.createElement("script");
  hm.src = "https://hm.baidu.com/hm.js?7e15ed96eb8133218e99de8bc1f5cb61";
  var s = document.getElementsByTagName("script")[0];
  s.parentNode.insertBefore(hm, s);
})();
</script>
       </div>
    </div> 
</body>
</html>
